package body Freetype2 is
   use Interfaces.C;

   procedure Check_Call(Result : FT_Error; Name : String)
   is
   begin
      if Result /= 0 then
         raise Freetype_Error with Name & " fail with error" & Result'Img;
      end if;
   end Check_Call;

   procedure Free (L : in out FT_Library)
   is
   begin
      FT2.Base.Done_Freetype(L, Error);
      Check_Call(Error, "FT_Done_Freetype");
   end Free;

   procedure Free (F : FT_Face)
   is
      Font : FT_Face := F;
   begin
      FT2.Base.Done_Face(Font, Error);
      Check_Call(Error, "FT_Done_Face");
   end Free;

   procedure Init
   is
   begin
      FT2.Base.Init_Freetype(Library, Error);
      Check_Call(Error, "FT_Init_Library");
   end Init;

   procedure Done
   is
   begin
      for Font of Fonts loop
         Free(Font);
      end loop;
      Fonts.Clear;
      FT2.Base.Done_Freetype(Library, Error);
   end Done;

   function Get_Font (Family : String) return FT_Face
   is
      C : Font_Table.Cursor := Fonts.Find(Family);
      F : FT_Face;
   begin
      if Font_Table.Has_Element(C) then
         return Font_Table.Element(C);
      end if;
      if Library = null then
         Init;
      end if;
      FT2.Base.New_Face(Library, Family, 0, F, Error);
      Check_Call(Error, "FT_New_Face");
      Select_Charmap(F, FT_ENCODING_UNICODE, Error);
      if Error /= 0 then
         Set_Charmap(F, To_Array(F.Charmaps, F.Num_Charmaps)(0), Error);
         Check_Call(Error, "Set_Charmap");
      end if;
      Fonts.Include(Family, F);
      return F;
   end Get_Font;

end Freetype2;
